<?php

namespace app\common\util;

use think\facade\Log;
use think\facade\Request;
use app\common\model\Spread;
use app\common\model\Product;
use app\common\exception\CatchException;
use app\common\service\WechatXcxService;

class ImageGenerator
{
    /**
     * 生成推广海报图，示例图见[figma](https://www.figma.com/file/mLLZaNSqZHVDTMzEXnXcVB/%E4%BA%91%E9%97%A8%E5%95%86%E5%9C%88%E8%90%A5%E9%94%80%E7%B3%BB%E7%BB%9F?type=design&node-id=1124-12447&mode=design&t=O0gI3U9IMTojF4z6-4)
     *
     * @param Product $product
     * @param int $spreadId
     * 
     * @return string 图片路径
     */
    public static function generateSpreadPicture(Product $product, Spread $spread)
    {
        static $AIM_WIDTH = 1100; //目标宽度
        static $SRC_BASE_X = 0;
        static $SRC_BASE_Y = 0;
        static $DST_BASE_X = 0;
        static $DST_BASE_Y = 0;

        $spreadId = $spread->id;
        // 构建需要的路径
        $publicPath = public_path(); //public目录
        $outputDir = "storage/spread/$spreadId/"; // 图片输出目录
        $publicUrl = Request::domain() . getVirRootDir() . '/' . $outputDir;
        $envVersion = match (EnvHelper::getReleaseType()) { // 确认小程序运行环境
            EnvHelper::RELEASE_TYPE_DEV => 'develop',
            EnvHelper::RELEASE_TYPE_TEST => 'trial',
            EnvHelper::RELEASE_TYPE_PROD => 'release',
            default => 'release'
        };
        $spreadPhotoName = "product_{$envVersion}_{$product->id}.jpg"; //推广图名称
        $publicUrl .= $spreadPhotoName; // 图片输出路径
        $localPath = $publicPath . $outputDir . $spreadPhotoName;
        $font = "static/font/simhei.ttf";
        $fontFile = $publicPath . $font;

        $scene = "p={$product->id}&sr={$spreadId}&path=prod&s={$product->spot_id}"; //小程序参数

        if (!file_exists($publicPath . $outputDir)) {
            mkdir($publicPath . $outputDir, 0777, true);
        }

        // 文件存在且创建时间未超过7天
        if (file_exists($localPath) && time() - filectime($localPath) <= 604800) {
            //如果海报图存在
            //return $publicUrl; //2023年11月17日10:04:14暂时先去掉缓存
        }

        // 生成小程序码
        $imageData = self::WechatAppService()->getUnlimit($scene, 'pages/index/index', $envVersion, 512);
        $小程序码 = imagecreatefromstring($imageData);

        $whiteBottomImg = imagecreatetruecolor(275, 72);
        $bgColor = imagecolorallocate($whiteBottomImg, 255, 255, 255); // 白色背景
        imagefill($whiteBottomImg, 0, 0, $bgColor);
        $bottomImg = ImageHelper::getImageInfoFromRawGdImage($whiteBottomImg, $AIM_WIDTH); //底部图片

        $spreadImgUrl = $product->spread_poster;
        if (!$spreadImgUrl) {
            throw new CatchException('未找到产品海报底图');
        }
        $mainImgObj = ImageHelper::getImageInfo($spreadImgUrl, $AIM_WIDTH); // 获取处理后主图片信息
        $xcxCodeObj = ImageHelper::getImageInfoFromRawGdImage($小程序码, 256, 256); // 获取处理后小程序码信息
        $avatar_url = $spread->member?->avatar_url;
        if ($avatar_url) {
            $用户头像 = ImageHelper::getImageInfo(getLocalPathFromRemoteUrl($spread->member->avatar_url), 96, 96); // 获取处理后用户头像信息
        }

        $canvas = ImageHelper::createCanvas($AIM_WIDTH, $mainImgObj['height'] + $bottomImg["height"]); // 画布
        $black = imagecolorallocate($canvas, 29, 33, 41); // 黑色画笔
        $grey = imagecolorallocate($canvas, 124, 144, 156); // 灰色画笔
        /**
         * bool imagecopyresampled ( resource $dst_image , resource $src_image , int $dst_x , int $dst_y , int $src_x , int $src_y , int $dst_w , int $dst_h , int $src_w , int $src_h )
         * dst_image    目标图象连接资源。
         * src_image    源图象连接资源。
         * dst_x    目标 X 坐标点。
         * dst_y    目标 Y 坐标点。
         * src_x    源的 X 坐标点。
         * src_y    源的 Y 坐标点。
         * dst_w    目标宽度。
         * dst_h    目标高度。
         * src_w    源图象的宽度。
         * src_h    源图象的高度。
         */
        // 拼接不同图片
        // 海报图
        imagecopyresampled(
            $canvas,
            $mainImgObj["image"],
            $DST_BASE_X,
            $DST_BASE_Y,
            $SRC_BASE_X,
            $SRC_BASE_Y,
            $mainImgObj["width"],
            $mainImgObj["height"],
            $mainImgObj["orgWidth"],
            $mainImgObj["orgHeight"]
        );
        // 底部分享图
        imagecopyresampled(
            $canvas,
            $bottomImg["image"],
            $DST_BASE_X,
            $DST_BASE_Y + $mainImgObj["height"],
            $SRC_BASE_X,
            $SRC_BASE_Y,
            $bottomImg["width"],
            $bottomImg["height"],
            $bottomImg["orgWidth"],
            $bottomImg["orgHeight"]
        );
        // 小程序码
        imagecopyresampled(
            $canvas,
            $xcxCodeObj["image"],
            $DST_BASE_X + 800,
            $DST_BASE_Y + $mainImgObj["height"] + 16,
            $SRC_BASE_X,
            $SRC_BASE_Y,
            260,
            260,
            $xcxCodeObj["orgWidth"],
            $xcxCodeObj["orgHeight"]
        );
        // 用户头像 这里不需要展示用户头像，要小程序码
        /*if ($avatar_url) {
            imagecopyresampled(
                $canvas,
                $用户头像["image"],
                $DST_BASE_X + 800,
                $DST_BASE_Y + $mainImgObj["height"] + 16,
                $SRC_BASE_X,
                $SRC_BASE_Y,
                260,
                260,
                $用户头像["orgWidth"],
                $用户头像["orgHeight"]
            );
        }*/

        // 产品名
        $productName = $product->getAttr('name');
        $nameArr = mb_str_split($productName, 16);
        $nameLen = count($nameArr);
        for ($i = 0; $i < $nameLen; $i++) {
            $name = $nameArr[$i];
            imagettftext(
                $canvas,
                33,
                0,
                $DST_BASE_X + 48,
                $DST_BASE_Y + $mainImgObj['height'] + 100 + (50 * $i),
                $black,
                $fontFile,
                $nameArr[$i]
            );
        }
        $name = $spread->getAttr("name");
        // 姓名
        imagettftext(
            $canvas,
            33,
            0,
            $DST_BASE_X + 48,
            $DST_BASE_Y + $mainImgObj['height'] + 250,
            $grey,
            $fontFile,
            "@$name 为你推荐"
        );

        // debug 输出到浏览器

        // ob_start();
        // imagejpeg($canvas);

        // end-of-debug 
        // hint: 使用如下代码输出到浏览器
        // hint: $data = ob_get_clean();
        // hint: return response($data, 200, ['Content-Type' => 'image/jpeg']);

        // 保存图
        imagejpeg($canvas, $localPath, 100);
        Log::info("pid:{$product->id}|sid:$spreadId 海报生成位置：$localPath");
        imagedestroy($canvas);

        // 输出构建
        return $publicUrl;
    }

    protected static function WechatAppService()
    {
        return new WechatXcxService(app());
    }
}